package com.itany.corejava.code08_常用类.内部类;

/**
 * @author 石小俊
 * @date 2023年05月04日 15:47
 */
public class Test02_局部内部类 {
    public static void main(String[] args) {
        MyOuter outer = new MyOuter();
        outer.show();
    }
}

class MyOuter {
    private String name = "admin";
    private int age;

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public int getAge() {
        return age;
    }

    public void setAge(int age) {
        this.age = age;
    }

    private void test() {
        System.out.println("这是外部类的private修饰的方法");
    }

    public void show() {
        String gender = "男";

        // 定义局部内部类
        class MyInner {
            private String name = "alice";
            private String phone = "13812345678";

            public String getName() {
                return name;
            }

            public void setName(String name) {
                this.name = name;
            }

            public String getPhone() {
                return phone;
            }

            public void setPhone(String phone) {
                this.phone = phone;
            }

            private void test() {
                System.out.println("这是内部类的private修饰的方法");
            }

            public void print() {
                System.out.println("*****************内部类方法*****************");
                // 可以访问内部类所在的方法属性
                // 在JDK8之前访问内部类所在的方法中的属性时,属性必须使用final修饰
                // 从JDK8开始,内部类所在的方法属性默认被final修饰,因此可以省略final
                System.out.println(gender);
                // 但是,此时的属性仍然是被final修饰的,因此,其值不可变
                // 此时如果内部类所在的方法修改了该属性的值。则默认不会添加final
                // gender = "女"; // 报错
                // 也可以访问外部类与内部类中所有成员
                System.out.println(phone);
                System.out.println(age);
                // 当内部类与外部类存在同名属性,默认访问内部类的属性
                System.out.println(name);
                // 如果想要访问外部类属性
                System.out.println(MyOuter.this.name);
                MyOuter outer = new MyOuter();
                System.out.println(outer.name);

                // 访问方法
                test();
                MyOuter.this.test();
                outer.test();
                System.out.println("*****************内部类方法结束*****************");

            }
        }

        System.out.println("*****************外部类方法*****************");
        // 此时修改gender的值,则gender不会被final修饰,内部类访问部分报错
        // gender = "女";
        // 局部内部类只能在内部类所在的方法中进行实例化
        MyInner inner = new MyInner();
        inner.print();
        // 当内部类与外部类中存在同名属性时
        // 在外部类方法中
        System.out.println(name);
        test();

        // 当外部类访问内部类所在方法的属性
        System.out.println(inner.name);
        inner.test();

        System.out.println("*****************外部类方法结束*****************");
    }

}
